From: Marco Trevisan (TreviƱo) Date: Mon, 27 May 2019 21:16:38 +0000 (-0500) Subject: windowMenu: Do actions requiring grab once ungrabbed X-Git-Tag: archive/raspbian/50.5-1+rpi1~1^2~845^2^2~170 X-Git-Url: https://dgit.raspbian.org/%22http://www.example.com/cgi/%22/%22http:/www.example.com/cgi/%22?a=commitdiff_plain;h=2b3ab3ececd2b70023547552b1acf84cbc4fecb1;p=gnome-shell.git windowMenu: Do actions requiring grab once ungrabbed Resizing or moving a window needs starting a keyboard grab. However, if the action is triggered by a menu entry activation it might not work as we already have already an active grab on input devices to manage the menu itself. So, possibly wait maximum 100ms for the current grab operation to be completed before trying go start a new one. Needs https://gitlab.gnome.org/GNOME/mutter/merge_requests/596 Fixes https://gitlab.gnome.org/GNOME/gnome-shell/issues/1326 https://gitlab.gnome.org/GNOME/gnome-shell/merge_requests/557 --- diff --git a/js/ui/windowMenu.js b/js/ui/windowMenu.js index 18bda4057..78b307db8 100644 --- a/js/ui/windowMenu.js +++ b/js/ui/windowMenu.js @@ -1,6 +1,6 @@ // -*- mode: js; js-indent-level: 4; indent-tabs-mode: nil -* -const { Meta, St } = imports.gi; +const { GLib, Meta, St } = imports.gi; const BoxPointer = imports.ui.boxpointer; const Main = imports.ui.main; @@ -42,13 +42,13 @@ var WindowMenu = class extends PopupMenu.PopupMenu { item.setSensitive(false); item = this.addAction(_("Move"), event => { - window.begin_grab_op(Meta.GrabOp.KEYBOARD_MOVING, true, event.get_time()); + this._grabAction(window, Meta.GrabOp.KEYBOARD_MOVING, event.get_time()); }); if (!window.allows_move()) item.setSensitive(false); item = this.addAction(_("Resize"), event => { - window.begin_grab_op(Meta.GrabOp.KEYBOARD_RESIZING_UNKNOWN, true, event.get_time()); + this._grabAction(window, Meta.GrabOp.KEYBOARD_RESIZING_UNKNOWN, event.get_time()); }); if (!window.allows_resize()) item.setSensitive(false); @@ -169,6 +169,26 @@ var WindowMenu = class extends PopupMenu.PopupMenu { if (!window.can_close()) item.setSensitive(false); } + + _grabAction(window, grabOp, time) { + if (global.display.get_grab_op() == Meta.GrabOp.NONE) { + window.begin_grab_op(grabOp, true, time); + return; + } + + let waitId = 0; + let id = global.display.connect('grab-op-end', (display) => { + display.disconnect(id); + GLib.source_remove(waitId); + + window.begin_grab_op(grabOp, true, time); + }); + + waitId = GLib.timeout_add(GLib.PRIORITY_DEFAULT, 100, () => { + global.display.disconnect(id); + return GLib.SOURCE_REMOVE; + }); + } }; var WindowMenuManager = class {